package com.lxq.www.controller;

import com.lxq.www.feigntemplate.MonitorRestInterface;
import com.netflix.hystrix.contrib.javanica.annotation.DefaultProperties;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixProperty;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpMethod;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;

import java.io.IOException;
import java.net.URI;

@RestController
@DefaultProperties(defaultFallback = "globalHystrixProcess")
public class DevController {

    @Autowired
    RestTemplate restTemplate;
    @Autowired
    MonitorRestInterface monitorRestInterface;

    @HystrixCommand
    @GetMapping("/sayTo")
    public String sayTo(String sayTo) throws IOException {
        System.out.println("sayTo=" + sayTo);
        var requestInput = restTemplate.getRequestFactory()
                .createRequest(URI.create(sayTo), HttpMethod.GET)
                .execute().getBody();
        var bytes = new byte[1024];
        var stringBuilder = new StringBuilder();
        while (requestInput.read(bytes) != -1) {
            stringBuilder.append(new String(bytes));
        }
        return stringBuilder.toString();
    }

    @HystrixCommand
    @GetMapping("/hello2")
    public String getRandomUuid() throws IOException {
        var factory = restTemplate.getRequestFactory()
                .createRequest(URI.create("http://CLOUD-MONITOR/hello2"), HttpMethod.GET).execute();
        var requestInput = factory.getBody();
        var bytes = new byte[1024];
        var stringBuilder = new StringBuilder();
        while (requestInput.read(bytes) != -1) {
            stringBuilder.append(new String(bytes));
        }
        return stringBuilder.toString();
    }

    @HystrixCommand
    @GetMapping("/hello3")
    public String helloFromFeign() {
        return monitorRestInterface.hello2();
    }

    @HystrixCommand
    @GetMapping("/sleep_req")
    public String reqSleep() {
        return monitorRestInterface.reqSleep();
    }

    @GetMapping("/sleep_req_out")
    public String reqOut() {
        return monitorRestInterface.reqOut();
    }

    @GetMapping("/sleep_req_out_2")
    @HystrixCommand
    public String sleepRequestTimeoutForHystrix() {
        return monitorRestInterface.reqOutForHystrix();
    }

    @GetMapping("/sleep_req_out_3")
    public String sleepRequestTimeoutInSelf() {
        return monitorRestInterface.reqOutForMyself();
    }

    public String globalHystrixProcess() {
        return "<h1>globalHystrixProcess：很抱歉，系统出现无法处理的异常</h1>";
    }


    @GetMapping("/hystrix_broker_divide")
    @HystrixCommand(fallbackMethod = "hystrixBrokerFallBack", commandProperties = {
            @HystrixProperty(name = "circuitBreaker.enabled", value = "true"),
            @HystrixProperty(name = "circuitBreaker.requestVolumeThreshold", value = "10"),
            @HystrixProperty(name = "circuitBreaker.errorThresholdPercentage", value = "6"),
            @HystrixProperty(name = "circuitBreaker.sleepWindowInMilliseconds", value = "10000")
    })
    public String hystrixBrokerTest(double numerator, double denominator) throws Exception {
        if (denominator == 0) throw new Exception("除数不能为零");
        return "计算结果：" + numerator + "÷" + denominator + "=" + (numerator / denominator);
    }

    public String hystrixBrokerFallBack(double numerator, double denominator) {
        return "<p style=\"colo:red\">计算错误：" + numerator + "÷" + denominator + "</p>";
    }
}
